local skynet = require "skynet"
local filelog = require "filelog"
local tabletool = require "tabletool"
local timetool = require "timetool"
local timer = require "timer"
local filename = "tablerequest.lua"
require "pubenum"
require "sssenum"

local tablerequest = {
	service = nil
}

function tablerequest.init(service)
	if tablerequest.service == nil then
		tablerequest.service = service
	end
end

function tablerequest.createtable(rid, roledata, msgbody)
	local server = tablerequest.service
	local table_data = server.table_data
	local responsemsg = {}
	skynet.send(".router", "lua", "clear_ridinfo", 0, rid, table_data.conf.table_index, table_data.conf.table_type)
	responsemsg.retcode = EErrCode.ERR_INVALID_PARAMS
	responsemsg.retstr = "参数不正确"
	return responsemsg
end

function tablerequest.entertraintable(rid, roledata)
	local server = tablerequest.service
	local table_data = server.table_data
	local responsemsg = {}
	skynet.send(".router", "lua", "clear_ridinfo", 0, rid, table_data.conf.table_index, table_data.conf.table_type)
	responsemsg.retcode = EErrCode.ERR_INVALID_PARAMS
	responsemsg.retstr = "稍等再进入"
	return responsemsg
end

function tablerequest.getpubtablelist(rid)
	local server = tablerequest.service
	local table_data = server.table_data
	local list = {
		mylist = {},
		publist = {},
	}
	skynet.send(".router", "lua", "clear_ridinfo", 0, rid, table_data.conf.table_index, table_data.conf.table_type)
	return list
end

function tablerequest.cancelmatch(rid, roledata, msgbody)
	local server = tablerequest.service
	local table_data = server.table_data
	local responsemsg = {}
	return responsemsg
end

function tablerequest.entertable(rid, roledata, msgbody)
	local responsemsg = {
	}
	local server = tablerequest.service
	local table_data = server.table_data
	local seatinfo, seat
	local roomtablelogic = server:get_logicbyname("tablelogic")
	local playerinfo = roledata.info
	----要关服了,不让玩家进入
	if table_data.table_end_flag == true then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = "服务器维护中"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end

	if table_data.conf.table_type == SSSTableType.TABLE_TYPE_FANGKA then
		----
		if table_data.curr_to_num >= 1 then
			responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
			responsemsg.retstr = "自建房游戏已经开始不能进入"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
	elseif table_data.conf.table_type == SSSTableType.TABLE_TYPE_ZUANSI or table_data.conf.table_type == SSSTableType.TABLE_TYPE_ZJZUANSI then
		----判断玩家身上的钱
		if roledata.money.diamond < table_data.conf.enter_diamond or roledata.money.diamond < roomtablelogic.get_tip() or roledata.money.diamond <= 0 then
			responsemsg.retcode = EErrCode.ERR_NOT_ENOUGH_DIAMOND
			responsemsg.retstr = "余额不足,不能继续游戏"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
		if table_data.conf.match_type ~= 0 then
			responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
			responsemsg.retstr = "不能直接进入匹配场"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
	elseif table_data.conf.table_type == SSSTableType.TABLE_TYPE_COIN then
		-----友豆场判断身上的友豆是否够入场和服务费
		if roledata.money.coin < table_data.conf.enter_diamond or roledata.money.coin < roomtablelogic.get_tip() 
			or roledata.money.coin <= 0 then
			responsemsg.retcode = EErrCode.ERR_NOT_ENOUGH_DIAMOND
			responsemsg.retstr = "余额不足,不能继续游戏"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
		if table_data.conf.match_type ~= 0 then
			responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
			responsemsg.retstr = "不能直接进入匹配场"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
	end
	seat = roomtablelogic.get_seat_by_rid(table_data, rid)
	local waitinfo = table_data.waits[rid]
	----判断房间是否已经满了
	if seat == nil and waitinfo == nil then
		if table_data.conf.cur_player_num >= table_data.conf.max_player_num then 
			responsemsg.retcode = EErrCode.ERR_TABLE_FULL
			responsemsg.retstr = "房间人数已满!"
			return responsemsg
		end
	end
	roomtablelogic.entertable(table_data, rid, msgbody, roledata, seat)
	if table_data.conf.table_type == SSSTableType.TABLE_TYPE_TRAIN then
		local trainlogic = server:get_logicbyname("trainlogic")
		trainlogic.check_all_mirror_readytime()
	end
	responsemsg.game_info = {
		table_baseinfo = {},
		table_conf = {},
		seat_baseinfo = {},
		seat_playerinfo = {},
	}
	roomtablelogic.copy_table_game_info(responsemsg.game_info)
	skynet.pcall(skynet.retpack, responsemsg)
	---有操作,更新心跳时间
	server:update_heart_time()
	if table_data.delete_table_timer_id > 0 then
		timer.cleartimer(table_data.delete_table_timer_id)
		table_data.delete_table_timer_id = -1
		table_data.is_deleting = false
	end
	skynet.sleep(50)
	 --自动坐下
    local result = tablerequest.sitdowntable(rid, roledata, {})
    ---filelog.sys_error("-------auto sitdowntable------", result)
    if not result or result.retcode ~= nil then
       skynet.pcall(skynet.retpack, result)
    end
end

function tablerequest.matchentertable(rid, roledata, msgbody)
	local server = tablerequest.service
	local table_data = server.table_data
	local responsemsg = {}
	local seatinfo, seat
	local roomtablelogic = server:get_logicbyname("tablelogic")
	local playerinfo = roledata.info
	----要关服了,不让玩家进入
	if table_data.table_end_flag == true then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = "服务器维护中"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end

	if table_data.is_deleting == true then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = "桌子将要删除"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end

	if table_data.conf.table_type == SSSTableType.TABLE_TYPE_FANGKA then
		----斗牛只有自建房卡模式才扣房卡
		----todo
	elseif table_data.conf.table_type == SSSTableType.TABLE_TYPE_ZUANSI then
		----判断玩家身上的钱
		if roledata.money.diamond < table_data.conf.enter_diamond or roledata.money.diamond < roomtablelogic.get_tip() or roledata.money.diamond <= 0 then
			responsemsg.retcode = EErrCode.ERR_NOT_ENOUGH_DIAMOND
			responsemsg.retstr = "余额不足,不能继续游戏"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
	elseif table_data.conf.table_type == SSSTableType.TABLE_TYPE_COIN then
		-----友豆场判断身上的友豆是否够入场和服务费
		if roledata.money.coin < table_data.conf.enter_diamond or roledata.money.coin < roomtablelogic.get_tip() 
			or roledata.money.coin <= 0 then
			responsemsg.retcode = EErrCode.ERR_NOT_ENOUGH_DIAMOND
			responsemsg.retstr = "您的金币不足，请前往充值"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
	end
	seat = roomtablelogic.get_seat_by_rid(table_data, rid)
	local waitinfo = table_data.waits[rid]
	if seat == nil and waitinfo == nil then
		----判断房间是否已经满了
		if table_data.conf.cur_player_num >= table_data.conf.max_player_num then 
			responsemsg.retcode = EErrCode.ERR_TABLE_FULL
			responsemsg.retstr = "房间人数已满!"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
	end
	if seat == nil then
		if waitinfo == nil then
			table_data.waits[rid] = {}
			waitinfo = table_data.waits[rid]
			waitinfo.playerinfo = {}
			table_data.waits[rid] = waitinfo
			table_data.cur_watch_playernum = table_data.cur_watch_playernum + 1			 
		end
		waitinfo.rid = rid
		waitinfo.gatesvr_id = "gatenode"
		waitinfo.is_mirror = false
		waitinfo.is_matching = true
		waitinfo.is_robot = false
		if roledata.is_robot == true then
			waitinfo.is_robot = true
		end
		waitinfo.playerinfo.rolename = roledata.info.rolename
		waitinfo.playerinfo.logo = roledata.info.rolename
		waitinfo.playerinfo.sex = roledata.info.sex
		waitinfo.playerinfo.diamond = roledata.money.diamond
		waitinfo.playerinfo.coin = roledata.money.coin
		waitinfo.playerinfo.fangka = roledata.money.fangka
		waitinfo.playerinfo.intro = roledata.info.intro
		waitinfo.playerinfo.ip_address = roledata.ip_addr
		waitinfo.playerinfo.upvoted_num = roledata.info.upvoted_num
		waitinfo.playerinfo.downvoted_num = roledata.info.downvoted_num
		waitinfo.playerinfo.gps_addr = roledata.gps_addr
		waitinfo.playerinfo.logoframe = roledata.info.logoframe
	end
	skynet.pcall(skynet.retpack, responsemsg)
	-- if table_data.delete_table_timer_id > 0 then
	-- 	timer.cleartimer(table_data.delete_table_timer_id)
	-- 	table_data.delete_table_timer_id = -1
	-- 	table_data.is_deleting = false
	-- end
end

function tablerequest.sitdowntable(rid, roledata, msgbody)
	local responsemsg = {}
	local server = tablerequest.service
	local table_data = server.table_data
	local seatinfo, seat
	local roomtablelogic = server:get_logicbyname("tablelogic")
	filelog.sys_error("-------------table.sitdowntable---------", msgbody)
	seat = roomtablelogic.get_seat_by_rid(table_data, rid)
	local playerinfo = roledata.info
	if seat ~= nil then
		seat.gatesvr_id = "node"
		seat.agent_address = -1
		seat.playerinfo.rolename = playerinfo.rolename
		seat.playerinfo.logo = playerinfo.logo
		seat.playerinfo.sex = playerinfo.sex
		seat.playerinfo.diamond = roledata.money.diamond
		seat.playerinfo.coin = roledata.money.coin
		seat.playerinfo.fangka = roledata.money.fangka
		seat.playerinfo.ip_address = roledata.ip_addr
		seat.playerinfo.intro = playerinfo.intro
		seat.playerinfo.upvoted_num = playerinfo.upvoted_num
		seat.playerinfo.downvoted_num = playerinfo.downvoted_num
		seat.playerinfo.gps_addr = roledata.gps_addr
		seat.playerinfo.logoframe = playerinfo.logoframe
		if table_data.waits[rid] then
			table_data.waits[rid] = nil
			if table_data.cur_watch_playernum > 0 then
				table_data.cur_watch_playernum = table_data.cur_watch_playernum - 1
			end
		end
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	else
		----要关服了,不让玩家进入
		if table_data.table_end_flag == true then
			if table_data.waits[rid] then
				table_data.waits[rid] = nil
				if table_data.cur_watch_playernum > 0 then
					table_data.cur_watch_playernum = table_data.cur_watch_playernum - 1
				end
				local ntcnotice = { rid = rid }
				server:send_notice_to_players({rid} , "leavetableN", ntcnotice, nil, nil)
			end
			responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
			responsemsg.retstr = "服务器维护中"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
		if table_data.conf.table_type == SSSTableType.TABLE_TYPE_FANGKA then
			----斗牛只有自建房卡模式才扣房卡
			----todo
		elseif table_data.conf.table_type == SSSTableType.TABLE_TYPE_ZUANSI then
			----判断玩家身上的钱
			if roledata.money.diamond < table_data.conf.enter_diamond or roledata.money.diamond < roomtablelogic.get_tip() or roledata.money.diamond <= 0 then
				if table_data.waits[rid] then
					table_data.waits[rid] = nil
					if table_data.cur_watch_playernum > 0 then
						table_data.cur_watch_playernum = table_data.cur_watch_playernum - 1
					end
					local ntcnotice = { rid = rid }
					server:send_notice_to_players({rid} , "leavetableN", ntcnotice, nil, nil)
				end
				responsemsg.retcode = EErrCode.ERR_NOT_ENOUGH_DIAMOND
				responsemsg.retstr = "您的元宝不足，请前往充值"
				skynet.pcall(skynet.retpack, responsemsg)
				return 
			end
		elseif table_data.conf.table_type == SSSTableType.TABLE_TYPE_COIN then
			-----友豆场判断身上的友豆是否够入场和服务费
			if roledata.money.coin < table_data.conf.enter_diamond or roledata.money.coin < roomtablelogic.get_tip() 
				or roledata.money.coin <= 0 then
				responsemsg.retcode = EErrCode.ERR_NOT_ENOUGH_DIAMOND
				responsemsg.retstr = "您的友豆不足，请前往充值"
				skynet.pcall(skynet.retpack, responsemsg)
				return 
			end
		end

		if roomtablelogic.is_full(table_data) then
			if table_data.waits[rid] then
				table_data.waits[rid] = nil
				if table_data.cur_watch_playernum > 0 then
					table_data.cur_watch_playernum = table_data.cur_watch_playernum - 1
				end
				local ntcnotice = { rid = rid }
				server:send_notice_to_players({rid} , "leavetableN", ntcnotice, nil, nil)
			end
			responsemsg.retcode = EErrCode.ERR_TABLE_FULL
			responsemsg.retstr = "房间人数已满！"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
		if msgbody.seat_index == 0 then
			seat = roomtablelogic.get_emptyseat_by_index(table_data, nil)
		else
			seat = roomtablelogic.get_emptyseat_by_index(table_data, msgbody.seat_index)
		end

		if seat == nil then
			if table_data.waits[rid] then
				table_data.waits[rid] = nil
				if table_data.cur_watch_playernum > 0 then
					table_data.cur_watch_playernum = table_data.cur_watch_playernum - 1
				end
				local ntcnotice = { rid = rid }
				server:send_notice_to_players({rid} , "leavetableN", ntcnotice, nil, nil)
			end
			responsemsg.retcode = EErrCode.ERR_NO_EMPTY_SEAT
			responsemsg.retstr = "房间人数已满!"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
		if seat.state ~= SSSSeatState.SEAT_STATE_NO_PLAYER then
			if table_data.waits[rid] then
				table_data.waits[rid] = nil
				if table_data.cur_watch_playernum > 0 then
					table_data.cur_watch_playernum = table_data.cur_watch_playernum - 1
				end
				local ntcnotice = { rid = rid }
				server:send_notice_to_players({rid} , "leavetableN", ntcnotice, nil, nil)
			end
			responsemsg.retcode = EErrCode.ERR_NOT_NO_PLAYER
			responsemsg.retstr = "座位不是没有玩家的状态！"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
		--增加桌子人数计数 
		table_data.sitdown_player_num = table_data.sitdown_player_num + 1
		table_data.conf.cur_player_num = table_data.conf.cur_player_num + 1		
	end
	---有操作,更新心跳时间
	server:update_heart_time()
	roomtablelogic.sitdowntable(table_data, msgbody, seat, roledata, rid)
	server:updateplayernum()
	if table_data.delete_table_timer_id > 0 then
		timer.cleartimer(table_data.delete_table_timer_id)
		table_data.delete_table_timer_id = -1
		table_data.is_deleting = false
	end
	skynet.pcall(skynet.retpack, responsemsg)
end

function tablerequest.matchsitdowntable(rid, roledata, msgbody)
	local responsemsg = {}
	local server = tablerequest.service
	local table_data = server.table_data
	if table_data.is_deleting == true then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = "服务器维护中"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	local seatinfo, seat
	local roomtablelogic = server:get_logicbyname("tablelogic")
	seat = roomtablelogic.get_seat_by_rid(table_data, rid)
	local playerinfo = roledata.info
	if seat ~= nil then
		seat.gatesvr_id = "node"
		seat.agent_address = -1
		seat.is_matching = true
		if roledata.is_robot == true then
			seat.is_robot = true
		else
			seat.is_robot = false
		end
		seat.playerinfo.rolename = playerinfo.rolename
		seat.playerinfo.logo = playerinfo.logo
		seat.playerinfo.sex = playerinfo.sex
		seat.playerinfo.coin = roledata.money.coin
		seat.playerinfo.diamond = roledata.money.diamond
		seat.playerinfo.fangka = roledata.money.fangka
		seat.playerinfo.ip_address = roledata.ip_addr
		seat.playerinfo.intro = playerinfo.intro
		seat.playerinfo.upvoted_num = playerinfo.upvoted_num
		seat.playerinfo.downvoted_num = playerinfo.downvoted_num
		seat.playerinfo.gps_addr = roledata.gps_addr
		seat.playerinfo.logoframe = playerinfo.logoframe
		seat.playerinfo.level = playerinfo.level
		if table_data.waits[rid] then
			table_data.waits[rid] = nil
			if table_data.cur_watch_playernum > 0 then
				table_data.cur_watch_playernum = table_data.cur_watch_playernum - 1
			end
		end
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	else
		----要关服了,不让玩家进入
		if table_data.table_end_flag == true then
			if table_data.waits[rid] then
				table_data.waits[rid] = nil
				if table_data.cur_watch_playernum > 0 then
					table_data.cur_watch_playernum = table_data.cur_watch_playernum - 1
				end
				local ntcnotice = { rid = rid }
				server:send_notice_to_players({rid} , "leavetableN", ntcnotice, nil, nil)
			end
			responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
			responsemsg.retstr = "服务器维护中"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end

		if table_data.conf.table_type == SSSTableType.TABLE_TYPE_FANGKA then
			----斗牛只有自建房卡模式才扣房卡
			----todo
		elseif table_data.conf.table_type == SSSTableType.TABLE_TYPE_ZUANSI then
			----判断玩家身上的钱
			if roledata.money.diamond < table_data.conf.enter_diamond or roledata.money.diamond < roomtablelogic.get_tip() or roledata.money.diamond <= 0 then
				if table_data.waits[rid] then
					table_data.waits[rid] = nil
					if table_data.cur_watch_playernum > 0 then
						table_data.cur_watch_playernum = table_data.cur_watch_playernum - 1
					end
					local ntcnotice = { rid = rid }
					server:send_notice_to_players({rid} , "leavetableN", ntcnotice, nil, nil)
				end
				responsemsg.retcode = EErrCode.ERR_NOT_ENOUGH_DIAMOND
				responsemsg.retstr = "余额不足,不能继续游戏"
				skynet.pcall(skynet.retpack, responsemsg)
				return 
			end
		elseif table_data.conf.table_type == SSSTableType.TABLE_TYPE_COIN then
			-----友豆场判断身上的友豆是否够入场和服务费
			if roledata.money.coin < table_data.conf.enter_diamond or roledata.money.coin < roomtablelogic.get_tip() 
				or roledata.money.coin <= 0 then
				responsemsg.retcode = EErrCode.ERR_NOT_ENOUGH_DIAMOND
				responsemsg.retstr = "余额不足,不能继续游戏"
				skynet.pcall(skynet.retpack, responsemsg)
				return 
			end
		end
		if roomtablelogic.is_full(table_data) then
			if table_data.waits[rid] then
				table_data.waits[rid] = nil
				if table_data.cur_watch_playernum > 0 then
					table_data.cur_watch_playernum = table_data.cur_watch_playernum - 1
				end
				local ntcnotice = { rid = rid }
				server:send_notice_to_players({rid} , "leavetableN", ntcnotice, nil, nil)
			end
			responsemsg.retcode = EErrCode.ERR_TABLE_FULL
			responsemsg.retstr = "房间人数已满!"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
		if msgbody.seat_index == 0 then
			seat = roomtablelogic.get_emptyseat_by_index(table_data, nil)
		else
			seat = roomtablelogic.get_emptyseat_by_index(table_data, msgbody.seat_index)
		end

		if seat == nil then
			if table_data.waits[rid] then
				table_data.waits[rid] = nil
				if table_data.cur_watch_playernum > 0 then
					table_data.cur_watch_playernum = table_data.cur_watch_playernum - 1
				end
				local ntcnotice = { rid = rid }
				server:send_notice_to_players({rid} , "leavetableN", ntcnotice, nil, nil)
			end
			responsemsg.retcode = EErrCode.ERR_NO_EMPTY_SEAT
			responsemsg.retstr = "房间人数已满!"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
		if seat.state ~= SSSSeatState.SEAT_STATE_NO_PLAYER then
			if table_data.waits[rid] then
				table_data.waits[rid] = nil
				if table_data.cur_watch_playernum > 0 then
					table_data.cur_watch_playernum = table_data.cur_watch_playernum - 1
				end
				local ntcnotice = { rid = rid }
				server:send_notice_to_players({rid} , "leavetableN", ntcnotice, nil, nil)
			end
			responsemsg.retcode = EErrCode.ERR_NOT_NO_PLAYER
			responsemsg.retstr = "座位不是没有玩家的状态！"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
		--增加桌子人数计数 
		table_data.sitdown_player_num = table_data.sitdown_player_num + 1
		table_data.conf.cur_player_num = table_data.conf.cur_player_num + 1		
	end
	roomtablelogic.matchsitdowntable(table_data, msgbody, seat, roledata, rid)
	server:updateplayernum()
	skynet.pcall(skynet.retpack, responsemsg)
	-- if table_data.delete_table_timer_id > 0 then
	-- 	timer.cleartimer(table_data.delete_table_timer_id)
	-- 	table_data.delete_table_timer_id = -1
	-- 	table_data.is_deleting = false
	-- end
end

function tablerequest.gameready(rid, roledata, msgbody)
	local responsemsg = {
	}
	local server = tablerequest.service
	local table_data = server.table_data
	local roomtablelogic = server:get_logicbyname("tablelogic")
	local seat = roomtablelogic.get_seat_by_rid(table_data, rid)
	if seat == nil then
		responsemsg.retcode = EErrCode.ERR_HAD_STANDUP
		responsemsg.retstr = "玩家不在座位上！"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	----要关服了,不让玩家进入
	if table_data.table_end_flag == true then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = "服务器维护中"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	if seat.state == SSSSeatState.SEAT_STATE_WAIT_START then
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	if seat.state ~= SSSSeatState.SEAT_STATE_WAIT_READY then
		responsemsg.retcode = EErrCode.ERR_HAD_STANDUP
		responsemsg.retstr = "座位状态不是等待准备状态！"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	if table_data.conf.table_type == SSSTableType.TABLE_TYPE_ZUANSI or table_data.conf.table_type == SSSTableType.TABLE_TYPE_ZJZUANSI then
		if roledata.money.diamond < table_data.conf.leave_diamond or roledata.money.diamond < roomtablelogic.get_tip() or roledata.money.diamond <= 0 then
			responsemsg.retcode = EErrCode.ERR_NOT_ENOUGH_DIAMOND
			responsemsg.retstr = "余额不足,不能继续游戏"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
		if seat.diamond < table_data.conf.leave_diamond or seat.diamond < roomtablelogic.get_tip() or seat.diamond <= 0 then
			responsemsg.retcode = EErrCode.ERR_NOT_ENOUGH_DIAMOND
			responsemsg.retstr = "余额不足,不能继续游戏"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
	elseif table_data.conf.table_type == SSSTableType.TABLE_TYPE_TRAIN then
		if seat.train_score < table_data.conf.leave_diamond or seat.train_score < roomtablelogic.get_tip() or seat.train_score <= 0 then
			responsemsg.retcode = EErrCode.ERR_HAD_STANDUP
			responsemsg.retstr = "练习场积分不足"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
	elseif table_data.conf.table_type == SSSTableType.TABLE_TYPE_COIN then
		if seat.coin < table_data.conf.leave_diamond or seat.coin < roomtablelogic.get_tip() or seat.coin <= 0 then
			responsemsg.retcode = EErrCode.ERR_NOT_ENOUGH_DIAMOND
			responsemsg.retstr = "余额不足,不能继续游戏"
			skynet.pcall(skynet.retpack, responsemsg)
			return 
		end
	end
	if seat.playerinfo.level == 99 then
		---filelog.sys_error("----roledata.money--------", roledata.money, seat.diamond)
		if seat.diamond ~= roledata.money.diamond then seat.diamond = roledata.money.diamond end
	end
	seat.state = SSSSeatState.SEAT_STATE_WAIT_START
	if seat.ready_timer_id > 0  then ---取消准备倒计时
		timer.cleartimer(seat.ready_timer_id)
		seat.ready_timer_id = -1
	end
	---有操作,更新心跳时间
	server:update_heart_time()
	roomtablelogic.gameready(table_data, msgbody, seat, roledata)
	skynet.pcall(skynet.retpack, responsemsg)
end

function tablerequest.doaction(rid, roledata, msgbody)
	--[[
	//玩家请求操作
	message doaction {	
		optional int32 action_type = 1; 			// 只有理牌一个操作(1 理牌)
		optional int32 deal_as_special = 2;  		// 是否按照特殊牌型结算(1 按照特殊牌型 2 按一般牌型)
		repeated up_cards_item sorted_cards = 3; 	// 理牌后的牌型
	}
	--]]
	local server = tablerequest.service
	local responsemsg = {}
	local Card_type = 0
	local server = tablerequest.service
	local table_data = server.table_data
	local roomtablelogic = server:get_logicbyname("tablelogic")
	local roomseatlogic = server:get_logicbyname("seatlogic")
	local replaywrite = server:get_logicbyname("replaywrite")
	local seat = roomtablelogic.get_seat_by_rid(table_data, rid)
	if table_data.tablerecords == nil then
        table_data.tablerecords = {}
    end
    if table_data.tablerecords.actions == nil then
        table_data.tablerecords.actions = {}
    end
	local actioninfos = table_data.tablerecords.actions
	if seat == nil then
		responsemsg.retcode = EErrCode.ERR_HAD_STANDUP
		responsemsg.retstr = "玩家不在座位上！"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	if seat.timer_id > 0 then
		timer.cleartimer(seat.timer_id)
		seat.timer_id = -1
	end
	---filelog.sys_error("------begin tablerequest.doaction------", rid, msgbody)
	if not msgbody.action_type or not msgbody.sorted_cards or #msgbody.sorted_cards == 0 then
		if not msgbody.sorted_cards or #msgbody.sorted_cards == 0 then
			if msgbody.deal_as_special ~= 1 then
				responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
				responsemsg.retstr = "上传的数据不正确!"
				skynet.pcall(skynet.retpack, responsemsg)
				return
			end
		end 
	end
	----理牌
	if seat.state == SSSSeatState.SEAT_STATE_SORTCARDS then
		if msgbody.action_type == SSSActionType.ACTION_SORTCARDS then
			---检查理牌上传上来的牌数据是否正确
			local deal_as_special = msgbody.deal_as_special
			if deal_as_special == 1 then
				if seat.special_card_type == 0 then
					responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
					responsemsg.retstr = "玩家没有特殊牌型"
					skynet.pcall(skynet.retpack, responsemsg)
					return
				else
					seat.deal_as_special = 1
					roomseatlogic.auto_sorted_cards(seat)
				end
			else
				local sorted_cards = msgbody.sorted_cards
				local card_isright = roomseatlogic.check_hand_cards(seat, sorted_cards)
				filelog.sys_error("---------card_isright-------", card_isright)
				if card_isright == false then
					responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
					responsemsg.retstr = "牌数据不正确"
					skynet.pcall(skynet.retpack, responsemsg)
					return 
				end
				local temp_sorted_items = {}
				for index, sorted_card in ipairs(sorted_cards) do
					temp_sorted_items[sorted_card.index] = {
						card_slot_index = sorted_card.index,
            			card_type = sorted_card.card_type,
            			deal_score = 0,
            			cards = tabletool.deepcopy(sorted_card.cards),
					}
				end
				--filelog.sys_error("----temp_sorted_items----", temp_sorted_items)
				local card_type_isright, err_no = roomseatlogic.check_sorted_cards(seat, temp_sorted_items)
				--filelog.sys_error("-----card_type_isright------", card_type_isright, err_no)
				if card_type_isright == false then
					filelog.sys_error("-----------analysize-------", temp_sorted_items, card_type_isright, err_no)
					--[[
					if err_no == 1 then
						responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
						responsemsg.retstr = "牌型不对"
						skynet.pcall(skynet.retpack, responsemsg)
						return 
					else
						responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
						responsemsg.retstr = "前道必须小于中道,中道必须小于尾道"
						skynet.pcall(skynet.retpack, responsemsg)
						return 
					end
					--]]
				end
				roomseatlogic.copy_sorted_items(seat, temp_sorted_items)
			end
			seat.state = SSSSeatState.SEAT_STATE_SORTCARDS_OVER
			seat.action_type = SSSActionType.ACTION_SORTCARDS
			roomtablelogic.waitdoaction(table_data, msgbody, seat, roledata)
		end
	else

	end
	filelog.sys_error("----------doaction------", rid, seat.index, msgbody)
	skynet.pcall(skynet.retpack, responsemsg)
	return 
end

function tablerequest.leavetable(rid, roledata, msgbody)
	local responsemsg = {}
	local server = tablerequest.service
	local table_data = server.table_data
	local seat
	local roomtablelogic = server:get_logicbyname("tablelogic")

	seat = roomtablelogic.get_seat_by_rid(table_data, rid)
	if seat == nil then
		roomtablelogic.leavetable(table_data, msgbody, seat, rid)
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	----如果玩家在游戏中,不能让他能够退出房间
	if table_data.conf.table_type == SSSTableType.TABLE_TYPE_TRAIN then
		skynet.pcall(skynet.retpack, responsemsg)
		local ntcnotice = { rid = seat.rid}
		local rids = roomtablelogic.getallrids(table_data)
		roomtablelogic.standuptable(table_data, msgbody, seat)
		server:send_notice_to_players(rids, "leavetableN", ntcnotice, nil, nil)
		roomtablelogic.leavetable(table_data, msgbody, seat, rid)
	elseif table_data.conf.table_type == SSSTableType.TABLE_TYPE_ZUANSI or table_data.conf.table_type == SSSTableType.TABLE_TYPE_FANGKA 
		or table_data.conf.table_type == SSSTableType.TABLE_TYPE_COIN or table_data.conf.table_type == SSSTableType.TABLE_TYPE_ZJZUANSI then
		if not roomtablelogic.is_onegameend(table_data) and seat.state ~= SSSSeatState.SEAT_STATE_WAIT_NEXT_GAME then
			if table_data.conf.table_type == SSSTableType.TABLE_TYPE_FANGKA and 
				(table_data.state == SSSTableState.TABLE_STATE_START_GAME or table_data.state == SSSTableState.TABLE_STATE_WAIT_START_GAME) then
			else
				responsemsg.retcode = EErrCode.ERR_PLAYER_IN_GAME
				responsemsg.retstr = "房间正在游戏中,不能退出！"
				skynet.pcall(skynet.retpack, responsemsg)
				return 
			end 
		end
		if table_data.conf.table_type == SSSTableType.TABLE_TYPE_FANGKA then
			if table_data.curr_to_num >= 1 and table_data.curr_to_num < table_data.conf.retain_to_num then
				responsemsg.retcode = EErrCode.ERR_PLAYER_IN_GAME
				responsemsg.retstr = "房卡场局数没有打完不能退出!!!"
				skynet.pcall(skynet.retpack, responsemsg)
				return 
			end
		end
		---skynet.pcall(skynet.retpack, responsemsg)
		local ntcnotice = { rid = seat.rid}
		local rids = roomtablelogic.getallrids(table_data)
		roomtablelogic.standuptable(table_data, msgbody, seat)
		server:send_notice_to_players(rids, "leavetableN", ntcnotice, nil, nil)
		roomtablelogic.leavetable(table_data, msgbody, seat, rid)
		if table_data.conf.table_type == SSSTableType.TABLE_TYPE_FANGKA and table_data.curr_to_num == 0 and rid == table_data.conf.create_user_rid then
			server:process("delete", "canceltable")
			return 
		end
	end
	---有操作,更新心跳时间
	server:update_heart_time()
	if table_data.conf.table_type == SSSTableType.TABLE_TYPE_FANGKA then return end
	---检查其他玩家是否准备好,如果准备好,则开始游戏
	if table_data.state == SSSTableState.DN_TABLE_STATE_WAIT_ALL_READY then
		if not roomtablelogic.has_real_player() then
			for index, seat in ipairs(table_data.seats) do
				if seat.rid ~= 0 and seat.is_mirror == true and seat.state == SSSSeatState.SEAT_STATE_WAIT_START then
					seat.state = SSSSeatState.SEAT_STATE_WAIT_READY
					seat.ready_to_time = 0
					if seat.ready_timer_id > 0 then
						timer.cleartimer(seat.ready_timer_id)
						seat.ready_to_time = -1
					end
				end
			end
		end

		local is_allready = roomtablelogic.check_all_ready(table_data)
		local readynum = 0
		for k, v in ipairs(table_data.seats) do
			if v.rid ~= 0 and v.state == SSSSeatState.SEAT_STATE_WAIT_START then
				readynum = readynum + 1
			end
		end
		if readynum > 1  and is_allready == true and table_data.state == SSSTableState.DN_TABLE_STATE_WAIT_ALL_READY then
			table_data.is_can_kick = false
			table_data.state = SSSTableState.DN_TABLE_STATE_ONE_GAME_START
			local gamelogic = roomtablelogic.get_gamelogic()
			gamelogic.run(table_data.gamelogic)
		elseif readynum <= 1 and is_allready == true then
			if table_data.conf.table_type == SSSTableType.TABLE_TYPE_TRAIN then
				if table_data.timer_id > 0 then
					timer.cleartimer(table_data.timer_id)
					table_data.timer_id =-1
				end
				local noticemsg = {
        			table_index = table_data.conf.table_index,
        			neednum = 1,
    			}
    			table_data.timer_id = timer.settimer(1*100, "train_add_mirror", noticemsg)
			end
		end
	end
	skynet.pcall(skynet.retpack, responsemsg)
end

function tablerequest.reentertable(rid, roledata, msgbody)
	local responsemsg = {}
	local server = tablerequest.service
	local table_data = server.table_data
	local seatinfo, seat, waitinfo
	local roomtablelogic = server:get_logicbyname("tablelogic")
	local roomseatlogic = server:get_logicbyname("seatlogic")
	local playerinfo = roledata.info

	seat = roomtablelogic.get_seat_by_rid(table_data, rid)
	if seat ~= nil then
		seatinfo = {
			index = seat.index,
		}
		seat.gatenode_id="node"
		seat.agent_address = -1
		seat.playerinfo.rolename = playerinfo.rolename
		seat.playerinfo.logo = playerinfo.logo
		seat.playerinfo.sex = playerinfo.sex
		seat.playerinfo.diamond = roledata.money.diamond
		seat.playerinfo.coin = roledata.money.coin
		seat.playerinfo.fangka = roledata.money.fangka
		seat.playerinfo.ip_address = roledata.ip_addr
		seat.playerinfo.intro = playerinfo.intro
		seat.playerinfo.upvoted_num = playerinfo.upvoted_num
		seat.playerinfo.downvoted_num = playerinfo.downvoted_num
		seat.playerinfo.gps_addr = roledata.gps_addr
		seat.playerinfo.logoframe = playerinfo.logoframe
		if table_data.conf.table_type == SSSTableType.TABLE_TYPE_ZUANSI then
			seat.diamond = roledata.money.diamond
		elseif table_data.conf.table_type == SSSTableType.TABLE_TYPE_ZJZUANSI then
			seat.diamond = roledata.money.diamond
		elseif table_data.conf.table_type == SSSTableType.TABLE_TYPE_COIN then
			seat.coin = roledata.money.coin
		end
	end

	if seat == nil then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = ""
		server:notice_tableinfo_togatenode("role_leave_table", rid, skynet.getenv("nodename"), table_data.conf.table_index)
		roomtablelogic.leavetable(table_data,  msgbody, nil, rid)
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	--[[
		//请求断线重连进入桌子
		message reentertable {
		}

		//响应断线重连进入桌子
		message reentertableR {	
			optional table_gameinfo game_info 		= 1; 
			optional int32 action_type 				= 2;
			optional int32 action_to_time 			= 3;
			optional int32 seat_index		 		= 4;
			optional int32 special_card_type        = 5; //特殊牌型
			repeated int32 hand_cards 				= 6; //手牌
			repeated player_gameend player_infos 	= 7; //座位上每个玩家的结算信息(结算了才会发,没结算为空)
		}
	--]]
	responsemsg.game_info = {
		table_baseinfo = {},
		table_conf = {},
		seat_baseinfo = {},
		seat_playerinfo = {},
	}
	if seat.state == SSSSeatState.SEAT_STATE_SORTCARDS_OVER then
		responsemsg.action_type = 0
		responsemsg.action_to_time = 0
	else
		responsemsg.action_type = seat.action_type
		responsemsg.action_to_time = seat.action_to_time
	end

	responsemsg.seat_index = seat.index
	responsemsg.special_card_type = seat.special_card_type
	responsemsg.hand_cards = nil
	responsemsg.player_infos = {}
	roomtablelogic.copy_table_game_info(responsemsg.game_info)

	if not roomtablelogic.is_onegameend(table_data) and seat ~= nil then
		responsemsg.hand_cards = tabletool.deepcopy(seat.cards)
	end
	if table_data.state == SSSTableState.TABLE_STATE_WAIT_ONE_GAME_END then
		roomtablelogic.copy_gameendinfo(responsemsg.player_infos)
		skynet.pcall(skynet.retpack, responsemsg)
	elseif table_data.state == SSSTableState.TABLE_STATE_WAIT_ALL_READY then
		skynet.pcall(skynet.retpack, responsemsg)
		if seat.state == SSSSeatState.SEAT_STATE_WAIT_READY then
			local doreadyntcmsg = {
		        rid = seat.rid,
		        seat_index = seat.index,
		        ready_to_time = seat.ready_to_time,
			}
			----避免匹配场在重进桌之前发消息给客户端
			--if seat.is_matching == false then
				server:send_notice_to_players({seat.rid}, "doreadyN", doreadyntcmsg, nil, nil)
			--end
		end
	else
		skynet.pcall(skynet.retpack, responsemsg)
	end
	if seat ~= nil then
		if seat.is_force_quit == 1 then
			seat.is_force_quit = 0
		end
		if seat.is_disconnected == 1 then
			seat.is_disconnected = 0
		end
		seat.is_matching = false
		local nowtime = timetool.get_time()
		if seat.state == SSSSeatState.SEAT_STATE_SORTCARDS and seat.action_to_time > nowtime then
			local action_time = seat.action_to_time - nowtime
			local noticemsg = {
                rid = seat.rid,
                seat_index = seat.index,
                action_to_time = seat.action_to_time,
                action_type = SSSActionType.ACTION_SORTCARDS,
            }
            local timernoticemsg = {
                table_index = table_data.conf.table_index,
                seat_index = seat.index,
                rid = seat.rid,
            }
            if seat.timer_id == -1 then
            	seat.timer_id = timer.settimer(action_time * 100, "sort_card_outoftime", timernoticemsg)
            end
            server:send_notice_to_players({seat.rid}, "todoN", noticemsg, nil, nil)
            ---seat.action_to_time = action_time + timetool.get_time()
		end 
	end
	---有操作,更新心跳时间
	server:update_heart_time()
	if seat.is_robot == false then
		server:notice_tableinfo_togatenode("role_enter_table", seat.rid, skynet.getenv("nodename"), table_data.conf.table_index)
	end
	if table_data.delete_table_timer_id > 0 then
		timer.cleartimer(table_data.delete_table_timer_id)
		table_data.delete_table_timer_id = -1
		table_data.is_deleting = false
	end
end

function tablerequest.disconnect(rid, roledata, msgbody)
	local server = tablerequest.service
	local table_data = server.table_data
	local roomtablelogic = server:get_logicbyname("tablelogic")
	local seat = roomtablelogic.get_seat_by_rid(table_data, rid)
	if seat ~= nil then
		seat.is_disconnected = 1
		---判断游戏是否开始,没开始游戏直接踢出玩家
		if seat.state == SSSSeatState.SEAT_STATE_WAIT_NEXT_GAME or seat.state == SSSSeatState.SEAT_STATE_WAIT_READY then
			roomtablelogic.passive_standuptable(table_data, nil, seat, SSSEStandupReason.STANDUP_REASON_DISCONNECTED)
			---检查其他玩家是否准备好,如果准备好,则开始游戏
			if table_data.state == SSSTableState.DN_TABLE_STATE_WAIT_ALL_READY then
				local is_allready = roomtablelogic.check_all_ready(table_data)
				local readynum = 0
				for k, v in ipairs(table_data.seats) do
					if v.rid ~= 0 and v.state == SSSSeatState.SEAT_STATE_WAIT_START then
						readynum = readynum + 1
					end
				end
				if readynum > 1  and is_allready == true and table_data.state == SSSTableState.DN_TABLE_STATE_WAIT_ALL_READY then
					table_data.is_can_kick = false
					table_data.state = SSSTableState.DN_TABLE_STATE_ONE_GAME_START
					local gamelogic = roomtablelogic.get_gamelogic()
					gamelogic.run(table_data.gamelogic)
				elseif readynum <= 1 and is_allready == true then
					if table_data.conf.table_type == SSSTableType.TABLE_TYPE_TRAIN then
						if table_data.timer_id > 0 then
							timer.cleartimer(table_data.timer_id)
							table_data.timer_id =-1
						end
						local noticemsg = {
        					table_index = table_data.conf.table_index,
        					neednum = 1,
    					}
    					table_data.timer_id = timer.settimer(1*100, "train_add_mirror", noticemsg)
					end
				end
			end
		end
	end
	local responsemsg = {
	}
	skynet.pcall(skynet.retpack, responsemsg)
end

function tablerequest.gettableconf(rid, roledata, msgbody)
	local responsemsg = {
	}
	local server = tablerequest.service
	local table_data = server.table_data
	local seatinfo, seat
	local roomtablelogic = server:get_logicbyname("tablelogic")
	local playerinfo = roledata.info
	if msgbody.table_index ~= table_data.conf.table_index then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = ""
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	responsemsg.table_conf = {}
	roomtablelogic.copy_table_conf(responsemsg.table_conf)
	skynet.pcall(skynet.retpack, responsemsg)
end

----已经进入牌桌,重复来的消息,不做处理直接返回成功
function tablerequest.entermatchtable(rid, roledata, msgbody)
	local responsemsg = {}
	skynet.pcall(skynet.retpack, responsemsg)
end

function tablerequest.entercoinmatchtable(rid, roledata, msgbody)
	local responsemsg = {}
	skynet.pcall(skynet.retpack, responsemsg)
end

function tablerequest.reentermatchtable(rid, roledata, msgbody)
	local responsemsg = {}
	skynet.pcall(skynet.retpack, responsemsg)
end

function tablerequest.get_tableinfo(table_index, rid)
	local server = tablerequest.service
	local tableobj = server.table_data
	local tablelogic = server:get_logicbyname("tablelogic")
	local seatlogic = server:get_logicbyname("seatlogic")
    local table_info = { }

    if rid then
        table_info.self_info = {}
        table_info.other_info = {}
        for _,seat in pairs(tableobj.seats) do
            if seat.state ~= SSSSeatState.SEAT_STATE_NO_PLAYER and seat.rid > 0  and seatlogic.is_ingame(seat) then
                if rid == seat.rid then
                    local item = {
                        rid = seat.rid,
                        seat_index = seat.index,
                        level = seat.playerinfo.level or 0,
                        cards_type = seat.cards_type,
                        cards = tabletool.deepcopy(seat.cards),
                    }
                    local cards_temp = tableobj.deal_cards_temp[seat.index]
					if cards_temp then
						if #item.cards == 0 then
							if #cards_temp == 5 then
								item.cards = tabletool.deepcopy(cards_temp)
							end
						elseif #item.cards == 4 then
							if #cards_temp == 1 then
								table.insert(item.cards, cards_temp[1])
							end
						end
					end
                    table_info.self_info = item
                else
                    local item = {
                        rid = seat.rid,
                        seat_index = seat.index,
                        level = seat.playerinfo.level or 0,
                        cards_type = seat.cards_type,
                        cards = tabletool.deepcopy(seat.cards)
                    }
                    local cards_temp = tableobj.deal_cards_temp[seat.index]
					if cards_temp then
						if #item.cards == 0 then
							if #cards_temp == 5 then
								item.cards = tabletool.deepcopy(cards_temp)
							end
						elseif #item.cards == 4 then
							if #cards_temp == 1 then
								table.insert(item.cards, cards_temp[1])
							end
						end
					end
                    table.insert(table_info.other_info,item)
                end
            end
        end
    else
        table_info.robot_rids = {}  --机器人rid列表
        if tableobj.seats and next(tableobj.seats) ~= nil then
        	for _,seat in pairs(tableobj.seats) do
            	if seat.playerinfo.level == 99 then
                	table.insert(table_info.robot_rids, { rid = seat.rid, total_score = seat.balance_total, game_num = seat.continue_games })
            	end
        	end
        else
        	skynet.pcall(skynet.retpack, table_info)
        	return 
        end
        local is_ingame = not tablelogic.is_onegameend(tableobj)
        table_info.table_index = tableobj.conf.table_index         --桌子索引
        table_info.state = tableobj.state               --桌子状态
        table_info.table_type = tableobj.conf.table_type     --桌子类型
        table_info.match_type = tableobj.conf.match_type     --匹配场类型
        table_info.is_ingame = is_ingame                --是否游戏中
        table_info.is_public = tableobj.conf.is_public  --是否公开桌
        table_info.cur_player = tableobj.conf.cur_player_num --当前玩家数
        table_info.max_player = tableobj.conf.max_player_num--最大玩家数
        table_info.base_score = tableobj.conf.score_diamond --桌子底注
        table_info.enter_score = tableobj.conf.enter_diamond--桌子入场底注
    end
    table_info.tableinfo = {
    	table_index = tableobj.conf.table_index,
		table_type = tableobj.conf.table_type,
		table_mode = tableobj.conf.table_mode,
		play_game_type = tableobj.conf.play_game_type,
		is_open_flush = tableobj.conf.is_open_flush,
		xia_zhu_type = tableobj.conf.xia_zhu_type,
		score_diamond = tableobj.conf.score_diamond,
		banker_seat_index = tableobj.banker_seat_index,
		in_game_num = 0,
	}
	table_info.seatinfo = {}
	for seat_index, seat in ipairs(tableobj.seats) do
		if seat.state ~= SSSSeatState.SEAT_STATE_NO_PLAYER and seatlogic.is_ingame(seat) then
			if table_info.seatinfo[seat.rid] == nil then
				table_info.seatinfo[seat.rid] = {
					rid = seat.rid,
					seat_index = seat.index,
					qiangzhuang_times = seat.qiangzhuang_times,
					xiazhu_times = seat.xiazhu_times,
					level = seat.playerinfo.level or 0,
					cards = tabletool.deepcopy(seat.cards),
				}
				local cards_temp = tableobj.deal_cards_temp[seat.index]
				if cards_temp then
					if #table_info.seatinfo[seat.rid].cards == 0 then
						if #cards_temp == 5 then
							table_info.seatinfo[seat.rid].cards = tabletool.deepcopy(cards_temp)
						end
					elseif #table_info.seatinfo[seat.rid].cards == 4 then
						if #cards_temp == 1 then
							table.insert(table_info.seatinfo[seat.rid].cards, cards_temp[1])
						end
					end
				end
			end
		end
		if seat.rid ~= 0 and seat.state ~= SSSSeatState.SEAT_STATE_WAIT_NEXT_GAME then
			table_info.tableinfo.in_game_num = table_info.tableinfo.in_game_num + 1
		end
	end
	skynet.pcall(skynet.retpack, table_info)
end

function tablerequest.disbandtable(rid, roledata, msgbody)
	local server = tablerequest.service
	local table_data = server.table_data

	local responsemsg = {}
	local tablelogic = server:get_logicbyname("tablelogic")

	if table_data.conf.table_type ~= SSSTableType.TABLE_TYPE_FANGKA then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = "不是自建桌,不能解散"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	
	local launch_player_seat = tablelogic.get_seat_by_rid(table_data, rid)
	if launch_player_seat == nil then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = "玩家不在座位上,不能取消！"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	---房间已经打过一局牌了
	local is_game_end = tablelogic.is_gameend(table_data)
	---filelog.sys_error("-------is_game_end------", table_data.curr_to_num, is_game_end)
	--[[
	//通知玩家响应桌子解散请求
	message disbandtableN {
		optional int32 rid = 1;
		optional int32 seat_index = 2;
		optional int32 action_timeout_time = 3;  //玩家操作到期时间
		optional string apply_player_name = 4;	//发起解散的玩家名字
		repeated player_disband_item player_disband_list = 5;	//玩家解散列表，所有玩家的响应情况
	}
	--]]
	
	----记录发起牌桌解散的玩家的行为
	table_data.cancel_tableinfo = {}
	table_data.cancel_tableinfo[launch_player_seat.index] = {
													index = launch_player_seat.index, 
													rid = launch_player_seat.rid, 
													action_type = DNActionType.ACTION_TYPE_AGREE,
													rolename = launch_player_seat.playerinfo.rolename,
												}
	--responsemsg.create_table_id = table_data.conf.create_table_id
	--responsemsg.wait_other = 1
	------广播所有玩家
	local disnoticemsg = {
		rid = launch_player_seat.rid,
		seat_index = launch_player_seat.index,
		action_timeout_time = timetool.get_time() + 100,
		apply_player_name = launch_player_seat.playerinfo.rolename,
		player_disband_list = {},
	}
	for index, actionobj in pairs(table_data.cancel_tableinfo) do
		local objbase = { rid = actionobj.rid, rolename = actionobj.rolename, is_agree = 0}
		if actionobj.action_type == DNActionType.ACTION_TYPE_AGREE then
			objbase.is_agree = 1
		elseif actionobj.action_type == DNActionType.ACTION_TYPE_DISAGREE then
			objbase.is_agree = 2
		end
		table.insert(disnoticemsg.player_disband_list, objbase)
	end

	for index, seat in ipairs(table_data.seats) do
		----发起者默认是同意解散,不发送操作通知给他
		if seat.rid ~= rid then
			local crequest = {
				rid = seat.rid,
				action_type = DNActionType.ACTION_TYPE_CHOICE,
				seat_index = seat.index,
				table_index = table_data.conf.table_index,
			}
			seat.cancel_timerid = timer.settimer(180*100, "timer_cancle_table", crequest)
			server:send_notice_to_players({seat.rid}, "disbandtableN", disnoticemsg, nil, nil)
		end
	end
	----判断本轮操作是否完成,完成则发送最终结果
	local isallover, lastaction, dis_index = tablelogic.check_allplayerdone()
	if isallover == true and lastaction == 1 then
		----直接调用大结算函数
		tablelogic.do_all_balance(table_data)
		skynet.pcall(skynet.retpack, responsemsg)
		server:process("delete", "canceltable")
		return 
	end

	---有操作,更新心跳时间
	server:update_heart_time()
	skynet.pcall(skynet.retpack, responsemsg)
end
--[[
//玩家请求同意或不同意
message disbanddeal {
	optional int32  id = 1;	
	optional int32  is_agree = 2;		//是否同意 1 同意 2 不同意
}
--]]
function tablerequest.disbanddeal(rid, roledata, msgbody)
	local server = tablerequest.service
	local table_data = server.table_data
	local responsemsg = {}
	local tablelogic = server:get_logicbyname("tablelogic")

	local seat = tablelogic.get_seat_by_rid(table_data, rid)
	if seat == nil then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = "玩家不在座位上！"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	----玩家已经完成操作,需要取消定时器
	if seat.cancel_timerid > 0 then
		timer.cleartimer(seat.cancel_timerid)
		seat.cancel_timerid = -1
	end
	----先判断玩家是否已经操作过
	local status = tablelogic.check_player_canceled(seat)
	if status == true then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = "你已经操作过"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	local rids = tablelogic.getallrids(table_data)
	----记录玩家在这轮的操作
	table_data.cancel_tableinfo[seat.index] = {
												index = seat.index, 
												rid = seat.rid,
												rolename = seat.playerinfo.rolename, 
												action_type = 0,
											}
	if msgbody.is_agree == 1 then
		table_data.cancel_tableinfo[seat.index].action_type = DNActionType.ACTION_TYPE_AGREE
	elseif msgbody.is_agree == 2 then
		table_data.cancel_tableinfo[seat.index].action_type = DNActionType.ACTION_TYPE_DISAGREE
	end
	----向其他玩家通知该玩家的操作结果
	--[[
		//广播玩家响应解散的结果
		message disbanddealN {
			optional int32 rid = 1;			//玩家rid
			optional string rolename = 2;	//玩家名字
			repeated player_disband_item player_disband_list = 3;	//玩家解散列表，所有玩家的响应情况
		}
		//响应解散的玩家信息
		message player_disband_item {
			optional int32 rid = 1;
			optional string rolename = 2;
			optional int32 is_agree = 3;		//是否同意, 1同意 2拒绝 nil未操作
		}
	--]]
	local noticemsg = {
		rid = seat.rid,
		rolename = seat.playerinfo.rolename,
		player_disband_list = {},
	}
	for index, actionobj in pairs(table_data.cancel_tableinfo) do
		local objbase = { rid = actionobj.rid, rolename = actionobj.rolename, is_agree = 0}
		if actionobj.action_type == DNActionType.ACTION_TYPE_AGREE then
			objbase.is_agree = 1
		elseif actionobj.action_type == DNActionType.ACTION_TYPE_DISAGREE then
			objbase.is_agree = 2
		end
		table.insert(noticemsg.player_disband_list, objbase)
	end
	server:send_notice_to_players(rids, "disbanddealN", noticemsg, nil, nil)

	----判断本轮操作是否完成,完成则发送最终结果
	local isallover, lastaction, dis_index = tablelogic.check_allplayerdone()
	if isallover == true then
		--[[
			//通知解散结果
		message disbandresultN {
			optional int32 table_index = 1; 	//桌号
			optional bool is_success = 2;		// 是否解散成功
		}
		--]]
		local noticeovermgs = {
			table_index = 0,
			is_success = "",
		}
		if lastaction == 2 then
			noticeovermgs.is_success = false
		elseif lastaction == 1 then
			noticeovermgs.is_success = true
		end
		---清除玩家操作记录
		table_data.cancel_tableinfo = {}
		server:send_notice_to_players(rids, "disbandresultN", noticeovermgs, nil, nil)
		if lastaction == 1 then
			----直接调用大结算函数
			tablelogic.do_all_balance(table_data)
			skynet.pcall(skynet.retpack, responsemsg)
			server:process("delete", "canceltable")
			return 
		end
	end
	---有操作,更新心跳时间
	server:update_heart_time()
	skynet.pcall(skynet.retpack, responsemsg)
end

function tablerequest.startgame(rid, roledata, msgbody)
	local server = tablerequest.service
	local table_data = server.table_data
	local responsemsg = {}
	local tablelogic = server:get_logicbyname("tablelogic")
	if table_data.conf.table_type ~= SSSTableType.TABLE_TYPE_FANGKA then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = "不是房卡场,不能主动开始游戏"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
	local seat = tablelogic.get_seat_by_rid(table_data, rid)
	if seat == nil then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = "没在桌内,不能开始游戏"
		skynet.pcall(skynet.retpack, responsemsg)
		return
	end
	if table_data.curr_to_num >= 1 then
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = "只有第一局才能主动开始游戏"
		skynet.pcall(skynet.retpack, responsemsg)
		return
	end
	-----判断桌子内所有玩家是否准备，且人数是否大于2人
	local is_allready, ready_num, is_one_leave = tablelogic.check_all_ready(table_data)
	local readynum = 0
	for k, v in ipairs(table_data.seats) do
		if v.rid ~= 0 and v.state == SSSSeatState.SEAT_STATE_WAIT_START then
			readynum = readynum + 1
		end
	end
	-----filelog.sys_error("-----------startgame------", readynum, is_allready, table_data.state)
	if readynum > 1  and is_allready == true and table_data.state == SSSTableState.DN_TABLE_STATE_WAIT_START_GAME then
		table_data.state = SSSTableState.DN_TABLE_STATE_ONE_GAME_START
		local rid_values = {}
		rid_values[seat.rid] = {
			value = 0,
			rolename = seat.playerinfo.rolename,
			beginvalue = seat.coin,
			endvalue = 0,
		}
		if table_data.conf.retain_to_num == 4 then
			rid_values[seat.rid].value = 200
			rid_values[seat.rid].endvalue = rid_values[seat.rid].beginvalue - rid_values[seat.rid].value
		elseif table_data.conf.retain_to_num == 8 then
			rid_values[seat.rid].value = 400
			rid_values[seat.rid].endvalue = rid_values[seat.rid].beginvalue - rid_values[seat.rid].value
		end
		seat.coin = seat.coin - rid_values[seat.rid].value
		seat.playerinfo.coin = seat.playerinfo.coin - rid_values[seat.rid].value
		tablelogic.game_sub_fangka(rid_values)
		skynet.pcall(skynet.retpack, responsemsg)
		local gamelogic = tablelogic.get_gamelogic()
		gamelogic.run(table_data.gamelogic)
		return 
	else
		responsemsg.retcode = EErrCode.ERR_INVALID_REQUEST
		responsemsg.retstr = "所有玩家还未准备完成"
		skynet.pcall(skynet.retpack, responsemsg)
		return 
	end
end

function tablerequest.delay_leave(rid, roledata, msgbody)
	---filelog.sys_error("-------------delay_leave---------", rid, roledata, msgbody)
	local server = tablerequest.service
	local table_data = server.table_data
	local responsemsg = {}
	local tablelogic = server:get_logicbyname("tablelogic")
	local seat = tablelogic.get_seat_by_rid(table_data, rid)
	if seat and seat.playerinfo.level == 99 then
		seat.is_delay_leave = true
	end
	skynet.pcall(skynet.retpack, responsemsg)
end

function tablerequest.update_table_player(table_index, cur_player_num, table_type, match_type, robot_num)
	local server = tablerequest.service
	local table_data = server.table_data
	local responsemsg = {}

	skynet.send(".router", "lua", "update_table_player", table_index, cur_player_num, 
			table_type, match_type, robot_num)
	skynet.pcall(skynet.retpack, responsemsg)
end 

--[[
	//
message movieover {
	
}

message movieoverR {
	
}
--]]
function tablerequest.movieover(rid, roledata, msgbody)
	local server = tablerequest.service
	local table_data = server.table_data
	local responsemsg = {}
	local nowtime = timetool.get_time()
	local next_ready_time = table_data.next_start_readytime
	filelog.sys_error("--------tablerequest.movieover------", rid, nowtime, next_ready_time)
	skynet.pcall(skynet.retpack, responsemsg)
end

return tablerequest